#!/bin/bash
set -e
set -o pipefail
# set -x
_filename=$0

SKIP_MYSQL=false
SKIP_REDIS=false
CHANGE_THIS_VERSION=""
DOCKER_COMPOSE_FILE=""
UPGRADE_DIR=~/dongtai_iast_upgrade
DESTORY_DATA=false
PROJECT_NAME=dongtai
REGISRTY=1

MYSQL_IP='dongtai-mysql:3306'
MYSQL_USERNAME='root'
MYSQL_PASSWORD='dongtai-iast'
MYSQL_DATABASES='dongtai_webapi'

DONGTAI_API="iast.huoxian.cn"
# DONGTAI_API="google.com"
DONGTAI_API_ACCESSABLE=true


DONGTAI_WEB_VER=""
DONGTAI_SERVER_VER=""
DONGTAI_REDIS_VER=""
DONGTAI_MYSQL_VER=""

Info() {
  echo -e "[Info] $1" >&2
}

Error() {
  echo -e "\033[31m[Error] $1 \033[0m" >&2
}

Todo() {
  echo -e "\033[36m[Todo] $1 \033[0m" >&2
}

Notice() {
  echo -e "\033[33m[Important] $1 \033[0m" >&2
}

Usage() {
  echo -e "\033[33m[Usage] $1 \033[0m" >&2
}

function print() {
  echo Print:$1 >&2
}

# Display usage message function
usage() {
  Info "Usage:"
  Usage "\t$_filename -h                                          Display usage message"
  Usage "\t$_filename install -s mysql,redis  -v 1.0.5            Install iast server"
  Usage "\t$_filename remove|rm [-d]                              Uninstall iast server"
  Usage "\t$_filename upgrade -t 1.1.2                            Upgrade iast server"
  Usage "\t$_filename version                                     Get image version"
  Usage "\t$_filename dbhash                                      Get database schema hash"
  Usage "\t$_filename dbschema                                    Export database schema"
  Usage "\t$_filename dbrestore -f FILEPATH                       Restore mysql database"
  Usage "\t$_filename dbbackup  -d FILEPATH                       Backup mysql database"
  Usage "\t$_filename file                                        Export docker-compose.yml "
  Usage "\t$_filename logs server|web|mysql|engine    Extract tail logs"
  Usage "\t$_filename start [PROJECT]                             Start all container,default project: dongtai"
  Usage "\t$_filename index                                       Initialize elasticsearch index"

}

OUT="$(uname -s)"
case "${OUT}" in
Linux*) machine=Linux ;;
Darwin*) machine=Mac ;;
CYGWIN*) machine=Cygwin ;;
MINGW*) machine=MinGw ;;
*) machine="UNKNOWN:${OUT}" ;;
esac
CURRENT_PATH=$(
  cd "$(dirname "$0")" || exit
)
cd "$CURRENT_PATH" || exit

sha=sha1sum
if [ $machine == "Mac" ]; then
  sha=shasum
fi

trim() {
  local trimmed="$1"
  # Strip leading spaces.
  while [[ $trimmed == ' '* ]]; do
    trimmed="${trimmed## }"
  done
  # Strip trailing spaces.
  while [[ $trimmed == *' ' ]]; do
    trimmed="${trimmed%% }"
  done
  echo "$trimmed"
}

function realpath() {
  [[ $1 == /* ]] && echo "$1" || echo "$PWD/${1#./}"
}

shell_path=$(realpath "$0")
shell_dir=$(dirname "$shell_path")

# compare version
function first_gt_second() {
  first=${1//./}
  second=${2//./}

  aa=$(( first - second ))
  if [ $aa -gt 0 ]; then
    echo true
  else
    echo false
  fi
}

# check if dongtai iast server is Running
function is_server_running() {
  if [ $(docker ps | grep "dongtai-web:" | wc -l) -gt 0 ]; then
    echo true
    return
  fi
  echo false
  return
}

# exit when server is not running
function exit_not_running() {
  if [ $(is_server_running) != true ]; then
    Error "Server is not running!"
    exit 1
  fi
}

# get docker-compose project_name
get_project_name() {
  retval=$(docker inspect --format='{{ index .Config.Labels "com.docker.compose.project" }}' $(docker ps | grep "dongtai-web:" | awk '{print $1}'))
  echo "$retval"
}
function current_image_version() {
  PROJECT_NAME=$(get_project_name)
  if [ -z $1 ]; then
    ver=$(docker ps  --filter "label=com.docker.compose.project=$PROJECT_NAME" | grep "dongtai-web:" | awk '{split($2,a,":");print a[2]}' | tail -n 1 )
  else
    ver=$(docker ps  --filter "label=com.docker.compose.project=$PROJECT_NAME" | grep "$1:" | awk '{split($2,a,":");print a[2]}'| tail -n 1 )
  fi
  echo "$ver"
}

function get_latest_release_version() {
  ver=$(cat updaterecord.txt | awk 'NR==2 {print $1}')
  echo "$ver"
}

function get_web_service_port() {
  PROJECT_NAME=$(get_project_name)
  WEB_CONTAINER_ID=$(docker ps  --filter "label=com.docker.compose.project=$PROJECT_NAME" | grep 'dongtai-web:' | awk '{print $1}')
  WEB_SERVICE_PORT=$(docker inspect --format='{{range $p, $conf := .NetworkSettings.Ports}} {{(index $conf 0).HostPort}} {{end}}' $WEB_CONTAINER_ID)
  WEB_SERVICE_PORT=$(trim $WEB_SERVICE_PORT)

  echo "$WEB_SERVICE_PORT"

}

# get mysql container id
function get_mysql_container_id() {
  mysql_container_id=""
  PROJECT_NAME=$(get_project_name)
  mysql_container_id=$(docker ps -a  --filter "label=com.docker.compose.project=$PROJECT_NAME" | grep "mysql" | awk '{print $1}')
  echo "$mysql_container_id"

}

# get server container id
function get_server_container_id() {
  server_container_id=""
  PROJECT_NAME=$(get_project_name)
  server_container_id=$(docker ps -a  --filter "label=com.docker.compose.project=dongtai" | grep "server" | awk '{print $NF}' | grep dongtai-server)
  echo "$server_container_id"

}

# check if image registry is in China
function get_image_registry() {
  if [ "$1" == 0 ]; then
    registry_url="dongtai"
  elif [ "$1" == 1 ]; then
    registry_url="registry.cn-beijing.aliyuncs.com/huoxian_pub"
  else
    registry_url=$(docker ps  --filter "label=com.docker.compose.project=$PROJECT_NAME" | grep "dongtai-web:" | awk 'i=index($2,"dongtai-web:") {print substr($2,0,i-2)}')
  fi
  echo "$registry_url"
}

# checkout network
function network() {
  local timeout=3
  local target=$DONGTAI_API
  local ret_code=$(curl -I -s --connect-timeout ${timeout} ${target} -w %{http_code} | tail -n1)
  if [ "$ret_code" == "200" ]; then
    echo true
    return
  else
    echo false
    return
  fi
  echo false
  return
}

 if [ ! $(network) == true ]; then
    Error "Internet unavailable."
    exit 1
  fi
# start to fetch the latest dtctl
# git pull

# get the latest docker image tag from

get_latest_image_tag_from_dockerhub() {
  image="$1"
  Info "start to get latest tag of $image"
  tags=`wget -q https://registry.hub.docker.com/v1/repositories/${image}/tags -O -  | sed -e 's/[][]//g' -e 's/"//g' -e 's/ //g' | tr '}' '\n'  | awk -F: '{print $3}'`

  if [ -n "$2" ]
  then
      tags=` echo "${tags}" | grep "$2" `
  fi
  echo "${tags}" | grep -E '^([0-9]+\.){0,2}(\*|[0-9]+)$' | tail -n 1
}

declare -a EXCLUDED_TABLES=(
  "dongtai_webapi.sca2_package"
  "dongtai_webapi.sca2_vul"
  "dongtai_webapi.sca2_vul_package"
  "dongtai_webapi.sca2_vul_package_range"
  "dongtai_webapi.sca2_vul_package_version"
  "dongtai_webapi.mysql_version_control"
  "dongtai_webapi.project_version_control"
)

IGNORED_TABLES_STRING=""
for TABLE in "${EXCLUDED_TABLES[@]}"; do
  :
  IGNORED_TABLES_STRING+=" --ignore-table=${TABLE} "
done

get_database_schema() {
  _mysql_container_id=$(get_mysql_container_id)
  if [ -z $_mysql_container_id ]; then
    Error "get_database_schema:mysql_container_id not exist"
    exit 1
  fi

  echo "dongtai-iast" | docker exec -i $_mysql_container_id /bin/bash -c "mysqldump -u root -d dongtai_webapi ${IGNORED_TABLES_STRING} -p --skip-set-charset --skip-comments --skip-opt | sed 's/ AUTO_INCREMENT=[0-9]*//g' | sed 's/\/\*!*.*//g' "
}

function current_hash() {
  retval=$(get_database_schema | $sha | awk '{print $1}')
  echo "$retval"
}

function get_database_data_dir() {
  mysql_id=$(get_mysql_container_id)
  if [ -z $mysql_id ]; then
    Notice "Mysql instance is not running"
    exit
  fi
  dir=$(docker inspect --format='{{range .Mounts}} {{.Source}} {{end}}' $(get_mysql_container_id))
  echo "$dir"
}

now=$(date '+%Y-%m-%d-%H-%M-%S')
function backup_mysql() {
  backup_dir=$UPGRADE_DIR
  if [ ! -z $1 ]; then
    backup_dir=$1
  fi
  backup_filename=$backup_dir/dongtai_iast-$now.sql
  mkdir -p $backup_dir
  Notice "Start to backup exist data,this will take a few minutes, don’t interrupt."
  docker exec -i $(get_mysql_container_id) /bin/bash -c "mysqldump -uroot -pdongtai-iast --single-transaction -R -E --default-character-set=utf8mb4 --databases 'dongtai_webapi' " >$backup_filename || exit 1
  Info "Finished backup exist data..."
  Info "$backup_filename"
}

function restore_mysql() {
  if [ -z $1 ]; then
    Error "Input data filepath."
    exit 1
  fi
  # before restore,backup current data
  backup_mysql
  Info "Start to restore data, data filepath: $1"
  docker exec -i $(get_mysql_container_id) /bin/bash -c "mysql -uroot -pdongtai-iast --default-character-set=utf8mb4 dongtai_webapi " <$1 || exit 1

  Notice "Database restore finished."

}

if [ $(is_server_running) == true ]; then
  if [ ! -z "$(get_mysql_container_id)" ]; then
    MOUNT_TYPE=$(docker inspect --format='{{range .Mounts}} {{.Type}} {{end}}' $(get_mysql_container_id))
  fi
fi

# check  network and modify config.ini
function check_network() {
  if [ $(network) == true ]; then
    Info "Dongtai Online API accessable!"
  else
    DONGTAI_API_ACCESSABLE=false
    if [ "$machine" == "Mac" ]; then
      sed -i '' 's/^base_url = https\:\/\/iast\.huoxian\.cn\/openapi\/sca\/v1/base_url = http:\/\/dongtai-server:8000\/sca\/v1/' config-tutorial.ini
    else
      sed -i 's/^base_url = https\:\/\/iast\.huoxian\.cn\/openapi\/sca\/v1/base_url = http:\/\/dongtai-server:8000\/sca\/v1/' config-tutorial.ini
    fi
    Info "Dongtai Online API unaccessable!"
  fi
}

# Info "Mount Type:$MOUNT_TYPE"

# create docker compose file
# Usage: create_docker_compose_file $VERSION $WEB_SERVICE_PORT $MYSQL_DATA_LOCATION
function create_docker_compose_file() {

  if [ ! -z "$1" ]; then
    CHANGE_THIS_VERSION=$1
  fi

  if [ ! -z "$2" ]; then
    WEB_SERVICE_PORT=$2
  fi

  if [ ! -z "$4" ] && [ $MOUNT_TYPE == "bind" ]; then
    _DATA_DIR=$3
  else
    _DATA_DIR="mysql-vol"
  fi
  Info "Data dir:$_DATA_DIR"
  MYSQL_STR=""
  REDIS_STR=""

  if [ "$3" == "install" ]; then
    if [ "$REGISRTY" == 1 ]; then
      registry=$(get_image_registry 1)
    else
      registry=$(get_image_registry 0)
    fi
  else
    registry=$(get_image_registry 2)
  fi

  if [ "$3" == "load_file" -o "$3" == "rm" ]; then
    DONGTAI_WEB_VER=$(current_image_version dongtai-web)
    DONGTAI_SERVER_VER=$(current_image_version dongtai-server)
    DONGTAI_REDIS_VER=$(current_image_version dongtai-redis)
    DONGTAI_MYSQL_VER=$(current_image_version dongtai-mysql)
  fi



  MYSQL_IMAGE_NAME="dongtai-mysql"
  if [ $DONGTAI_API_ACCESSABLE == false ]; then
    if [[ $(first_gt_second $CHANGE_THIS_VERSION 1.2.0) == true ]]; then
      MYSQL_IMAGE_NAME="dongtai-mysql-sca"
    fi
  fi

  if [ $DONGTAI_API_ACCESSABLE == false ]; then
    if [[ $(first_gt_second $CHANGE_THIS_VERSION 1.8.2) == true ]]; then
      MYSQL_IMAGE_NAME="dongtai-mysql"
    fi
  fi


  if [ $SKIP_MYSQL == false ]; then
    export MYSQL_STR=$(
      cat <<EOF
dongtai-mysql: 
    image: $registry/$MYSQL_IMAGE_NAME:$DONGTAI_MYSQL_VER
    restart: always
    volumes:
      - "$_DATA_DIR:/var/lib/mysql:rw"
      #- "/var/lib/mysql"
    logging:
      driver: "json-file"
      options:
        max-size: "10m"
EOF
    )
  elif [[ $(first_gt_second $CHANGE_THIS_VERSION 1.7.9) == true ]]; then
    read -p "请输入您的数据库IP和端口: 如 127.0.0.1:3306:" MYSQL_IP
    read -p "请输入您的数据库用户: 如 root:" MYSQL_USERNAME
    read -p "请输入您的数据库密码: 如 123456:" MYSQL_PASSWORD
    read -p "请输入您创建好的数据库名: 如 dongtai:" MYSQL_DATABASES
  fi

  if [ $SKIP_REDIS == false ]; then
    export REDIS_STR=$(
      cat <<EOF
dongtai-redis:
    image: $registry/dongtai-redis:$DONGTAI_REDIS_VER
    restart: always
    logging:
      driver: "json-file"
      options:
        max-size: "10m"

EOF
    )
  fi

  if [[ $(first_gt_second $CHANGE_THIS_VERSION 1.8.1) == true ]]; then
     read -r -d '' DOCKER_COMPOSE_FILE <<EOM
version: "2"
services:
  $MYSQL_STR
  $REDIS_STR
  dongtai-web:
    image: $registry/dongtai-web:$DONGTAI_WEB_VER
    restart: always
    ports:
      - "$WEB_SERVICE_PORT:80"
    volumes:
      - "$PWD/nginx.conf-1.8.0:/etc/nginx/nginx.conf"
    depends_on:
      - dongtai-server
    logging:
      driver: "json-file"
      options:
        max-size: "10m"
  dongtai-server:
    image: "$registry/dongtai-server:$DONGTAI_SERVER_VER"
    restart: always
    sysctls:
      net.core.somaxconn: 1024
    volumes:
      - iast-vol:/tmp/logstash/
      - $PWD/config-tutorial.ini:/opt/dongtai/dongtai_conf/conf/config.ini
    logging:
      driver: "json-file"
      options:
        max-size: "10m"
  dongtai-worker-task:
    image: "$registry/dongtai-server:$DONGTAI_SERVER_VER"
    restart: always
    entrypoint: ["/opt/dongtai/deploy/docker/entrypoint.sh", "beat"]
    volumes:
      - $PWD/config-tutorial.ini:/opt/dongtai/dongtai_conf/conf/config.ini
    logging:
      driver: "json-file"
      options:
        max-size: "10m"
  dongtai-worker-beat:
    image: "$registry/dongtai-server:$DONGTAI_SERVER_VER"
    restart: always
    entrypoint: ["/opt/dongtai/deploy/docker/entrypoint.sh", "worker-beat"]
    volumes:
      - $PWD/config-tutorial.ini:/opt/dongtai/dongtai_conf/conf/config.ini
    logging:
      driver: "json-file"
      options:
        max-size: "10m"
  dongtai-worker-other:
    image: "$registry/dongtai-server:$DONGTAI_SERVER_VER"
    restart: always
    entrypoint: ["/opt/dongtai/deploy/docker/entrypoint.sh", "worker-other"]
    volumes:
      - $PWD/config-tutorial.ini:/opt/dongtai/dongtai_conf/conf/config.ini
    logging:
      driver: "json-file"
      options:
        max-size: "10m"
  dongtai-worker-high-freq:
    image: "$registry/dongtai-server:$DONGTAI_SERVER_VER"
    restart: always
    entrypoint: ["/opt/dongtai/deploy/docker/entrypoint.sh", "worker-high-freq"]
    volumes:
      - $PWD/config-tutorial.ini:/opt/dongtai/dongtai_conf/conf/config.ini
    logging:
      driver: "json-file"
      options:
        max-size: "10m"
  dongtai-worker-sca:
    image: "$registry/dongtai-server:$DONGTAI_SERVER_VER"
    restart: always
    entrypoint: ["/opt/dongtai/deploy/docker/entrypoint.sh", "worker-sca"]
    volumes:
      - $PWD/config-tutorial.ini:/opt/dongtai/dongtai_conf/conf/config.ini
    logging:
      driver: "json-file"
      options:
        max-size: "10m"
  dongtai-worker-es:
    image: "$registry/dongtai-server:$DONGTAI_SERVER_VER"
    restart: always
    entrypoint: ["/opt/dongtai/deploy/docker/entrypoint.sh", "worker-es"]
    volumes:
      - $PWD/config-tutorial.ini:/opt/dongtai/dongtai_conf/conf/config.ini
    logging:
      driver: "json-file"
      options:
        max-size: "10m"
  dongtai-logrotate:
    image: "$registry/dongtai-logrotate:$DONGTAI_SERVER_VER"
    restart: always
    user: root
    volumes:
      - iast-vol:/tmp/logstash/
    logging:
      driver: "json-file"
      options:
        max-size: "10m"
  dongtai-logstash:
    image: "$registry/dongtai-logstash:$DONGTAI_SERVER_VER"
    restart: always
    user: root
    environment:
      - DATABASE=${MYSQL_IP}/${MYSQL_DATABASES}
      - USERNAME=${MYSQL_USERNAME}
      - PASSWORD=${MYSQL_PASSWORD}
    volumes:
      - iast-vol:/tmp/logstash/
    logging:
      driver: "json-file"
      options:
        max-size: "10m"
volumes:
  mysql-vol:
  iast-vol:
EOM
  elif [[ $(first_gt_second $CHANGE_THIS_VERSION 1.7.9) == true ]]; then
     read -r -d '' DOCKER_COMPOSE_FILE <<EOM
version: "2"
services:
  $MYSQL_STR
  $REDIS_STR
  dongtai-web:
    image: $registry/dongtai-web:$DONGTAI_WEB_VER
    restart: always
    ports:
      - "$WEB_SERVICE_PORT:80"
    volumes:
      - "$PWD/nginx.conf-1.8.0:/etc/nginx/nginx.conf"
    depends_on:
      - dongtai-server
    logging:
      driver: "json-file"
      options:
        max-size: "10m"
  dongtai-server:
    image: "$registry/dongtai-server:$DONGTAI_SERVER_VER"
    restart: always
    sysctls:
      net.core.somaxconn: 1024
    volumes:
      - iast-vol:/tmp/logstash/
      - $PWD/config-tutorial.ini:/opt/dongtai/dongtai_conf/conf/config.ini
    logging:
      driver: "json-file"
      options:
        max-size: "10m"
  dongtai-worker-task:
    image: "$registry/dongtai-server:$DONGTAI_SERVER_VER"
    restart: always
    entrypoint: ["/opt/dongtai/deploy/docker/entrypoint.sh", "beat"]
    volumes:
      - $PWD/config-tutorial.ini:/opt/dongtai/dongtai_conf/conf/config.ini
    logging:
      driver: "json-file"
      options:
        max-size: "10m"
  dongtai-worker-beat:
    image: "$registry/dongtai-server:$DONGTAI_SERVER_VER"
    restart: always
    entrypoint: ["/opt/dongtai/deploy/docker/entrypoint.sh", "worker-beat"]
    volumes:
      - $PWD/config-tutorial.ini:/opt/dongtai/dongtai_conf/conf/config.ini
    logging:
      driver: "json-file"
      options:
        max-size: "10m"
  dongtai-worker-other:
    image: "$registry/dongtai-server:$DONGTAI_SERVER_VER"
    restart: always
    entrypoint: ["/opt/dongtai/deploy/docker/entrypoint.sh", "worker-other"]
    volumes:
      - $PWD/config-tutorial.ini:/opt/dongtai/dongtai_conf/conf/config.ini
    logging:
      driver: "json-file"
      options:
        max-size: "10m"
  dongtai-worker-high-freq:
    image: "$registry/dongtai-server:$DONGTAI_SERVER_VER"
    restart: always
    entrypoint: ["/opt/dongtai/deploy/docker/entrypoint.sh", "worker-high-freq"]
    volumes:
      - $PWD/config-tutorial.ini:/opt/dongtai/dongtai_conf/conf/config.ini
    logging:
      driver: "json-file"
      options:
        max-size: "10m"
  dongtai-logrotate:
    image: "$registry/dongtai-logrotate:$DONGTAI_SERVER_VER"
    restart: always
    user: root
    volumes:
      - iast-vol:/tmp/logstash/
    logging:
      driver: "json-file"
      options:
        max-size: "10m"
  dongtai-logstash:
    image: "$registry/dongtai-logstash:$DONGTAI_SERVER_VER"
    restart: always
    user: root
    environment:
      - DATABASE=${MYSQL_IP}/${MYSQL_DATABASES}
      - USERNAME=${MYSQL_USERNAME}
      - PASSWORD=${MYSQL_PASSWORD}
    volumes:
      - iast-vol:/tmp/logstash/
    logging:
      driver: "json-file"
      options:
        max-size: "10m"
volumes:
  mysql-vol:
  iast-vol:
EOM
  elif [[ $(first_gt_second $CHANGE_THIS_VERSION 1.3.1) == true ]]; then
     read -r -d '' DOCKER_COMPOSE_FILE <<EOM
version: "2"
services:
  $MYSQL_STR
  $REDIS_STR
  dongtai-web:
    image: $registry/dongtai-web:$DONGTAI_WEB_VER
    restart: always
    ports:
      - "$WEB_SERVICE_PORT:80"
    volumes:
      - "$PWD/nginx.conf:/etc/nginx/nginx.conf"
    depends_on:
      - dongtai-server
    logging:
      driver: "json-file"
      options:
        max-size: "10m"
  dongtai-engine:
    image: "$registry/dongtai-server:$DONGTAI_SERVER_VER"
    restart: always
    entrypoint: ["/opt/dongtai/webapi/docker/entrypoint.sh", "worker"]
    volumes:
      - $PWD/config-tutorial.ini:/opt/dongtai/webapi/conf/config.ini
    logging:
      driver: "json-file"
      options:
        max-size: "10m"
  dongtai-server:
    image: "$registry/dongtai-server:$DONGTAI_SERVER_VER"
    restart: always
    volumes:
      - $PWD/config-tutorial.ini:/opt/dongtai/webapi/conf/config.ini
    logging:
      driver: "json-file"
      options:
        max-size: "10m"
  dongtai-engine-task:
    image: "$registry/dongtai-server:$DONGTAI_SERVER_VER"
    restart: always
    entrypoint: ["/opt/dongtai/webapi/docker/entrypoint.sh", "beat"]
    volumes:
      - $PWD/config-tutorial.ini:/opt/dongtai/webapi/conf/config.ini
    logging:
      driver: "json-file"
      options:
        max-size: "10m"
volumes:
  mysql-vol:

EOM

  else
  read -r -d '' DOCKER_COMPOSE_FILE <<EOM
version: "2"
services:
  $MYSQL_STR
  $REDIS_STR
  dongtai-webapi:
    image: "$registry/dongtai-webapi:$CHANGE_THIS_VERSION"
    restart: always
    volumes:
      - "$PWD/config-tutorial.ini-legacy:/opt/dongtai/webapi/conf/config.ini"
    logging:
      driver: "json-file"
      options:
        max-size: "10m"
    depends_on:
      - dongtai-mysql
  dongtai-web:
    image: "$registry/dongtai-web:$CHANGE_THIS_VERSION"
    restart: always
    ports:
      - "$WEB_SERVICE_PORT:80"
    volumes:
      - "$PWD/nginx.conf-legacy:/etc/nginx/nginx.conf"
    depends_on:
      - dongtai-webapi
    logging:
      driver: "json-file"
      options:
        max-size: "10m"
  dongtai-openapi:
    image: "$registry/dongtai-openapi:$CHANGE_THIS_VERSION"
    restart: always
    volumes:
       - "$PWD/config-tutorial.ini-legacy:/opt/dongtai/openapi/conf/config.ini"
    logging:
      driver: "json-file"
      options:
        max-size: "10m"
    depends_on:
      - dongtai-mysql
  dongtai-engine:
    image: "$registry/dongtai-engine:$CHANGE_THIS_VERSION"
    restart: always
    volumes:
      - "$PWD/config-tutorial.ini-legacy:/opt/dongtai/engine/conf/config.ini"
    logging:
      driver: "json-file"
      options:
        max-size: "10m"
    depends_on:
      - dongtai-mysql
  dongtai-engine-task:
    image: "$registry/dongtai-engine:$CHANGE_THIS_VERSION"
    restart: always
    command: ["/opt/dongtai/engine/docker/entrypoint.sh", "task"]
    volumes:
      - "$PWD/config-tutorial.ini-legacy:/opt/dongtai/engine/conf/config.ini"
    depends_on:
      - dongtai-engine
      - dongtai-mysql
    logging:
      driver: "json-file"
      options:
        max-size: "10m"
volumes:
  mysql-vol:
EOM

  fi

  echo "$DOCKER_COMPOSE_FILE"

}

if [ ! 0 == $# ]; then # If options provided then
  while getopts ":h" opt; do # Go through the options
    case $opt in
    h) # Help
      usage
      exit 0 # Exit correctly
      ;;
    ?) # Invalid option
      echo "[ERROR]: Invalid option: -${OPTARG}"
      usage
      exit 1 # Exit with erro
      ;;
    esac
  done
  shift $((OPTIND - 1))
  subcommand=$1
  shift # Get subcommand and shift to next option
  case "$subcommand" in
  "debug")
    result=$(get_latest_image_tag_from_dockerhub dongtai/dongtai-server)
    echo ""
    echo "result:$result"
    ;;
  "version")
    exit_not_running
    cur_ver=$(current_image_version)
    echo ""
    Notice "current image version: $cur_ver"
    ;;

  "start")
    shift $((OPTIND - 1))
    op=$1
    _project_name="dongtai"
    if [ ! -z $op ]; then
      _project_name=$op
    fi
    containers=$(docker ps -aq  --filter "label=com.docker.compose.project=$_project_name")
    Info $_project_name
    if [[ ! -n $containers ]]; then
      Notice "No containers found in project:$_project_name".
      exit
    else
      docker start $containers
      another_containers=$(docker ps -aq  --filter "label=com.docker.compose.project=dongtai-iast")
       if [[ -n $another_containers ]]; then
        docker start $another_containers
      fi
    fi
    ;;
  "dbhash")
    exit_not_running
    cur_hash=$(current_hash)

    Notice "current db hash: $cur_hash"
    ;;
  "dbschema")
    exit_not_running
    outout_filename="export_db_schema.txt"
    output_location="$shell_dir/$outout_filename"
    if [ ! 0 == $# ]; then # if options provided
      while getopts ":o:h" opt; do
        case "$opt" in
        "o")
          output_location=$OPTARG
          echo "$output_location"
          ;;
        "h")
          Usage "\t$_filename dbschema -o output_location                Export database schema"
          exit 1
          ;;
        ?) # Invalid option
          Error "Invalid option: -${OPTARG}"
          usage
          exit 1 # Exit with erro
          ;;
        esac
      done
    fi
    Info "Start export database schema to: $output_location"
    get_database_schema >$output_location || exit 1
    echo ""
    Notice "Exported database schema to: $output_location"
    ;;

  "dbbackup")
    exit_not_running
    if [ ! 0 == $# ]; then # if options provided
      while getopts ":d:h" opt; do
        case "$opt" in
        "d")
          data_location=$OPTARG
          ;;
        "h")
          Usage "\t$_filename dbbackup -d FILEPATH                         Backup mysql database"
          exit 1
          ;;
        ?) # Invalid option
          Error "Invalid option: -${OPTARG}"
          usage
          exit 1 # Exit with erro
          ;;
        esac
      done
    fi
    if [ -z "$data_location" ]; then
      backup_mysql
    else
      backup_mysql $data_location
    fi

    ;;

  "dbrestore")
    if [ ! 0 == $# ]; then # if options provided
      while getopts ":f:h" opt; do
        case "$opt" in
        "f")
          data_location=$OPTARG
          ;;
        "h")
          Usage "\t$_filename restore -f FILEPATH                         Restore mysql database"
          exit 1
          ;;
        ?) # Invalid option
          Error "Invalid option: -${OPTARG}"
          usage
          exit 1 # Exit with erro
          ;;
        esac
      done
    fi
    if [ -z "$data_location" ]; then
      Error "Data filepath required."
      exit 1
    else
      restore_mysql $data_location
    fi

    ;;

  "file")
    exit_not_running
    compose_file=$(create_docker_compose_file $(current_image_version) $(get_web_service_port) load_file $(get_database_data_dir) ) 
    file_path="$shell_dir/docker-compose.yml"
    Info "File location:$file_path"
    echo "$compose_file" >$file_path | exit 1
    ;;

  "logs")
    exit_not_running
    shift $((OPTIND - 1))
    op=$1
    shift
    PROJECT_NAME=$(get_project_name)
    docker logs -f --tail=200 $(docker ps | grep $PROJECT_NAME | grep "dongtai-$op:" | awk '{print $1}') || exit 1
    ;;
  "install") # install iast server
    #unset OPTIND
    # Check if the Docker service is turned on
    check_docker() {
      Info "check docker servie status."
      docker ps 1>/dev/null 2>/dev/null

      if [ $? -ne 0 ]; then
        Error "docker service is down. please start docker service and rerun."
        exit
      else
        Info "docker service is up."
      fi
    }

    check_docker_compose() {
      if ! [ -x "$(command -v docker-compose)" ]; then
        Error 'docker-compose not installed.'
        exit 1
      fi
    }

    # Info "mysql persistence"
    # mkdir data
    start_docker_compose() {
      Info "Starting docker compose ..."

      if [ ! -z "$1" ]; then
        docker_compose_file=$(create_docker_compose_file $CHANGE_THIS_VERSION $WEB_SERVICE_PORT "install" $1)
      else
        docker_compose_file=$(create_docker_compose_file $CHANGE_THIS_VERSION $WEB_SERVICE_PORT "install")
      fi

      if [ "$docker_compose_file" = "" ]; then
        Error "Create docker-compose.yaml error"
        exit 1
      fi

      docker-compose -p $PROJECT_NAME -f <(echo "$docker_compose_file") up -d --remove-orphans
    }

    # Specify the port of Web, OpenAPI service and check whether it is available
    check_port() {
      Info "check port status"

      is_port_inuse=false

      read -p "[+] please input web service port, default [80]:" WEB_SERVICE_PORT
      if [ -z "$WEB_SERVICE_PORT" ]; then
        WEB_SERVICE_PORT=80
      fi

      if ! [ -x "$(command -v lsof)" ]; then
        if [ $(netstat -tunlp | grep $WEB_SERVICE_PORT | grep "LISTEN" | wc -l || true) -gt 0 ]; then
          is_port_inuse=true
        fi
      else
        if [ $(lsof -i:$WEB_SERVICE_PORT | grep "LISTEN" | wc -l || true) -gt 0 ]; then
          is_port_inuse=true
        fi
      fi

      if [ $is_port_inuse == true ]; then
        Error "port $WEB_SERVICE_PORT is already in use. please change default port."
        exit
      else
        Info "port $WEB_SERVICE_PORT is ok."
      fi

    }

    DATA_DIR="$shell_dir/data"
    if [ ! 0 == $# ]; then # if options provided
      while getopts ":d:m:s:v:r:h:" optname; do
        case "$optname" in
        "d")
          DATA_DIR=$OPTARG
          ;;
        "s")
          SKIP=$OPTARG
          array=(${SKIP//,/ })
          for var in "${array[@]}"; do
            if [ "$var" == "mysql" ]; then
              SKIP_MYSQL=true
            elif [ "$var" == "redis" ]; then
              SKIP_REDIS=true
            fi
          done
          ;;
        "v")
          CHANGE_THIS_VERSION=$OPTARG
          ;;
        "r")
          REGISRTY=$OPTARG
          ;;
        "h")
          usage
          exit 1
          ;;
        ":")
          Error "option -${OPTARG} requires an argument"
          usage
          exit 1
          ;;
        "?")
          Error "Invalid option: -${OPTARG}"
          usage
          exit 1 # Exit with erro
          ;;
        esac
      done
    fi

    if [ -z "$CHANGE_THIS_VERSION" ] || [ "$CHANGE_THIS_VERSION" == "" ]; then
      # CHANGE_THIS_VERSION=$(get_latest_release_version)
        Info $CHANGE_THIS_VERSION
        DONGTAI_WEB_VER=$(get_latest_image_tag_from_dockerhub dongtai/dongtai-web)
        DONGTAI_SERVER_VER=$(get_latest_image_tag_from_dockerhub dongtai/dongtai-server)
        DONGTAI_REDIS_VER=$(get_latest_image_tag_from_dockerhub dongtai/dongtai-redis)
        DONGTAI_MYSQL_VER=$(get_latest_image_tag_from_dockerhub dongtai/dongtai-mysql)
        CHANGE_THIS_VERSION=$DONGTAI_MYSQL_VER
    else
      DONGTAI_WEB_VER=$CHANGE_THIS_VERSION
      DONGTAI_SERVER_VER=$CHANGE_THIS_VERSION
      DONGTAI_REDIS_VER=$CHANGE_THIS_VERSION
      DONGTAI_MYSQL_VER=$CHANGE_THIS_VERSION
    fi



    check_network
    check_docker
    check_docker_compose
    check_port
    #start_docker_compose "$DATA_DIR"
    start_docker_compose

    if [ $? -ne 0 ]; then
      Error "Installation failed,Something wrong!"
      exit
    else
      Notice "Installation success!"
    fi

    ;;
  "remove" | "rm")
    exit_not_running
    if [ ! 0 == $# ]; then # if options provided
      while getopts ":d:h:" opt; do
        case ${1} in
        "-d")
          DESTORY_DATA=true
          ;;
        "-h")
          Usage "\t$_filename rm [-d]                   Uninstall iast server"
          exit 1
          ;;
        ?) # Invalid option
          Error "Invalid option: -${OPTARG}"
          usage
          exit 1 # Exit with erro
          ;;
        esac
      done
    fi

    docker_compose_file=$(create_docker_compose_file $(current_image_version) $(get_web_service_port) "rm")

    PROJECT_NAME=$(get_project_name)
    if [ "$DESTORY_DATA" == true ]; then
      data_dir=$(get_database_data_dir)
      Notice "Data volume will be deleted."
      docker-compose -p $PROJECT_NAME -f <(echo "$docker_compose_file") down -v
      #docker volume rm dongtai_iast-vol
      if [ "$MOUNT_TYPE" == "bind" ]; then
        Notice "Data will be deleted in $data_dir"
        rm -rf $data_dir
      fi
    else
      docker-compose -p $PROJECT_NAME -f <(echo "$docker_compose_file") down
    fi
    ;;

  "upgrade")
    exit_not_running
    TO_VERSION=""
    FROM_VERSION=""
    SHA_FILE=updaterecord.txt
    WEB_CONTAINER_ID=$(docker ps | grep $PROJECT_NAME | grep 'dongtai-web:' | awk '{print $1}')

    function check_update_record_file() {
      if [ ! -f "$SHA_FILE" ]; then
        Error "$SHA_FILE does not exists!"
        exit
      fi
    }

    function check_schema_hash() {
      Info "Check database schema ..."

      # cat updaterecord.txt | awk "{ if($1==$FROM_VERSION) print $4}"

      FROM_DB_HASH=$(cat updaterecord.txt | awk -v FROM_VERSION=$FROM_VERSION '{ if($1==FROM_VERSION) print $4}')
      CURRENT_DATABASE_HASH=$(current_hash)

      Info "FROM_DB_HASH:$FROM_DB_HASH"
      Info "CURRENT_DATABASE_HASH:$CURRENT_DATABASE_HASH"

      if [ ! $CURRENT_DATABASE_HASH == $FROM_DB_HASH ]; then
        Error "Your current database hash value  not equals to the verison $FROM_VERSION, please check."
        exit
      fi

      Info "Database schema correct ..."
    }

    function execute_update() {
      # extract sql name and reverse list

      SQL_NAMES=$(cat updaterecord.txt | awk "/${TO_VERSION//./\\.}/,/${FROM_VERSION//./\\.}/ {print \$2}" | grep -vF "$FROM_VERSION" | awk "{array[NR]=\$0} END { for(i=NR;i>0;i--) {print array[i];} }")
      mysql_container_id=$(get_mysql_container_id)
      server_container_id=$(get_server_container_id)
      # check whether mysql is ready
      while :; do
        Info "start to check mysql status ..."
        tables=$(docker exec -i $mysql_container_id /bin/bash -c "mysql -uroot -p'dongtai-iast'  --execute \"SHOW DATABASES;\"" || true)
        if [[ ${tables["mysql"]} ]]; then
          Notice "mysql instance ready!"
          break
        fi
        sleep 2
      done

      # change sql store directory from /docker-entrypoint-initdb.d to /sql
      # from 1.3.0
      sql_dir="/docker-entrypoint-initdb.d"
      if [[ $(first_gt_second $TO_VERSION 1.2.0) == true ]]; then
        sql_dir="/sql"
      fi

      Info "Sql store directory: $sql_dir"

      # sql downloaded,start to execute sql
      Info $SQL_NAMES
      for SQL in $SQL_NAMES; do
        Info "Start to load sql:[$SQL]"
        docker exec -i $mysql_container_id /bin/bash -c "mysql -uroot -p'dongtai-iast' dongtai_webapi < $sql_dir/$SQL"
      done
      if [ $TO_VERSION = 1.8.0 ]; then
        docker exec -i $mysql_container_id /bin/bash -c "mysql -uroot -p'dongtai-iast' dongtai_webapi < $sql_dir/utf8mb4_general_ci.sql"
        Info "Sql character ok!"
        docker exec -i $server_container_id /bin/bash -c "python manage.py update"
      else
        Info "mysql character set check completed OK!!"
      fi
    }

    function check_after_execute() {
      Info "Check result..."
      TO_DB_HASH=$(cat updaterecord.txt | awk -v TO_VERSION=$TO_VERSION '{ if($1==TO_VERSION) print $4}')
      CURRENT_DATABASE_HASH=$(current_hash)

      Info "TO_DB_HASH:$TO_DB_HASH"
      Info "CURRENT_DATABASE_HASH:$CURRENT_DATABASE_HASH"

      if [ ! $CURRENT_DATABASE_HASH == $TO_DB_HASH ]; then
        Error "Your current database hash value not equals to the target:$TO_DB_HASH."
        Error "Did you change the database schema manually?"
        exit
      fi

      Info "Current database schema correct ..."
      Info "Upgrade Success ..."
    }

    function upgrade_docker_image() {
      WEB_PORT=$(docker inspect --format='{{range $p, $conf := .NetworkSettings.Ports}} {{(index $conf 0).HostPort}} {{end}}' $WEB_CONTAINER_ID)
      WEB_PORT=$(trim $WEB_PORT)

      # 创建 DOCKER_COMPOSE_FILE
      docker_compose_file=$(create_docker_compose_file $TO_VERSION $(get_web_service_port) $(get_database_data_dir) "upgrade")
      PROJECT_NAME=$(get_project_name)
      Info "Start to pull new images with tag $TO_VERSION"
      docker-compose -p $PROJECT_NAME -f <(echo "$docker_compose_file") pull

      Info "Start new containers with tag $TO_VERSION "
      docker-compose -p $PROJECT_NAME -f <(echo "$docker_compose_file") up -d --remove-orphans

    }

    function summary() {
      Notice "-----Upgrade summary start-----"
      Info "Ugrade from $FROM_VERSION to $TO_VERSION. \n"
      Info "Backup file : $backup_filename"
      Info "Executed sql as follow: "
      for SQL in $SQL_NAMES; do
        Info $SQL
      done
      Info "Ugrade workdir is $UPGRADE_DIR, this can be delete after upgraded. "
      Notice "-----Upgrade summary end-----"
    }

    if [ ! 0 == $# ]; then # if options provided
      while getopts ":t:h" optname; do
        case "$optname" in
        "t")
          TO_VERSION=$OPTARG
          ;;
        "h")
          Usage "\t$_filename upgrade -f 1.0.5 -t 1.1.2   Upgrade iast server"
          exit 1
          ;;
        ":") ;;

        "?")
          Error "Unknown option $OPTARG"
          exit 1
          ;;
        esac
      done
    fi

    FROM_VERSION=$(current_image_version)
    UPGRADE_TO_VERSION=$TO_VERSION
    if [ -z "$TO_VERSION" ]; then
      TO_VERSION=$(get_latest_release_version)
      UPGRADE_TO_VERSION="latest"
      DONGTAI_WEB_VER=$(get_latest_image_tag_from_dockerhub dongtai/dongtai-web)
      DONGTAI_SERVER_VER=$(get_latest_image_tag_from_dockerhub dongtai/dongtai-server)
      DONGTAI_REDIS_VER=$(get_latest_image_tag_from_dockerhub dongtai/dongtai-redis)
      DONGTAI_MYSQL_VER=$(get_latest_image_tag_from_dockerhub dongtai/dongtai-mysql)
    else
      DONGTAI_WEB_VER=$TO_VERSION
      DONGTAI_SERVER_VER=$TO_VERSION
      DONGTAI_REDIS_VER=$TO_VERSION
      DONGTAI_MYSQL_VER=$TO_VERSION
    fi

    Info "Upgrade: $FROM_VERSION -> $UPGRADE_TO_VERSION"

    f_gt_t=$(first_gt_second $FROM_VERSION $TO_VERSION)

    if [[ $f_gt_t == true ]]; then
      Error "Your current verison is $FROM_VERSION, you can upgrade to later version. $TO_VERSION is invalid."
      exit 1
    fi

    check_network
    backup_mysql
    check_update_record_file
    #check_schema_hash
    upgrade_docker_image
    execute_update
    #check_after_execute
    summary

    ;;
  "index")
    ES_HOST=""
    ES_ALIAS="dongtai-iast"
    if [ ! 0 == $# ]; then # if options provided
      while getopts ":t" optname; do
        case "$optname" in
        "t")
          read -p "请输入您要创建的 elasticsearch 索引前缀名: 如 dongtai-iast :" ES_ALIA
          if [ -z "$ES_ALIA" ]; then
            Info "将使用默认前缀名: $ES_ALIAS"
          else
            ES_ALIAS=$(echo $ES_ALIA | tr "[A-Z]" "[a-z]" | sed 's/[^ -z]/x/g')
            Info "索引前缀名已经转换为小写 请记录 $ES_ALIAS"
          fi
          ;;
        ":") ;;
        "?")
          Error "Unknown option $OPTARG"
          exit 1
          ;;
        esac
      done
    fi
    function dongtai_es() {
      read -p "请输入您的 elasticsearch 地址: 如 http://127.0.0.1:9200   :" ES_IP
      read -p "请输入您的 elasticsearch 用户: 如 elastic (无密码直接回车):" ES_USERNAME
      read -p "请输入您的 elasticsearch 密码: 如 123456  (无密码直接回车):" ES_PASSWORD
      if [ -z "$ES_USERNAME" ]; then
        ES_HOST=$ES_IP
      else
        ES_APP=$(echo $ES_IP | sed "s#//# #g")
        ARR=($ES_APP)
        ES_HOST=${ARR[0]}//${ES_USERNAME}:${ES_PASSWORD}@${ARR[1]}
      fi
      Info $ES_HOST
      ES_CODE=`curl -I -m 10 -o /dev/null -s -w %{http_code} ${ES_HOST}`
      if [ $ES_CODE -eq 200 ]; then
        Info $ES_CODE
      else
         Info "Please check that your elasticsearch configuration is correct !!!"
        exit 1
      fi
    }

    function dongtai_index() {
      Notice "-----index create-----"
      Info "index created   $ES_HOST  !!!"
      #ilm
      curl -H 'content-Type:application/json' -XPUT ${ES_HOST}/_ilm/policy/${ES_ALIAS}-dongtai-ilm-policy -d '
      {
        "policy": {
          "phases": {
            "hot": {
              "min_age": "0ms",
              "actions": {
                "rollover": {
                  "max_age": "90d",
                  "max_size": "60gb"
                },
                "set_priority": {
                  "priority": 999
                }
              }
            }
          }
        }
      }'
      #template-dongtai-v1-method-pool
      curl -H 'content-Type:application/json' -XPUT ${ES_HOST}/_template/${ES_ALIAS}-dongtai-v1-method-pool-template?include_type_name -d '
      {
        "order": 1,
        "index_patterns": [
          "'${ES_ALIAS}'-dongtai-v1-method-pool-index-*"
        ],
        "settings": {
          "index": {
            "lifecycle": {
              "name": "'${ES_ALIAS}'-dongtai-ilm-policy",
              "rollover_alias": "'${ES_ALIAS}'-alias-dongtai-v1-method-pool"
            },
            "highlight": {
              "max_analyzed_offset": "10000000"
            },
            "refresh_interval": "30s",
            "analysis": {
              "analyzer": {
                "ngram_analyzer": {
                  "tokenizer": "ngram_tokenizer"
                }
              },
              "tokenizer": {
                "ngram_tokenizer": {
                  "token_chars": [
                    "letter",
                    "digit",
                    "symbol",
                    "punctuation"
                  ],
                  "min_gram": "1",
                  "type": "ngram",
                  "max_gram": "2"
                }
              }
            },
            "number_of_shards": "4",
            "number_of_replicas": "1"
          }
        },
        "mappings": {
          "_doc": {
            "dynamic": "true",
            "_meta": {},
            "_source": {
              "includes": [],
              "excludes": []
            },
            "dynamic_date_formats": [
              "strict_date_optional_time",
              "yyyy/MM/dd HH:mm:ss Z||yyyy/MM/dd Z"
            ],
            "dynamic_templates": [],
            "date_detection": true,
            "numeric_detection": false,
            "properties": {
              "@timestamp": {
                "type": "date"
              },
              "agent_id": {
                "type": "integer"
              },
              "bind_project_id": {
                "type": "long"
              },
              "clent_ip": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword"
                  }
                }
              },
              "context_path": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword",
                    "ignore_above": 256
                  }
                }
              },
              "create_time": {
                "type": "date",
                "ignore_malformed": false,
                "format": "strict_date_optional_time||epoch_second"
              },
              "http_method": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword"
                  }
                }
              },
              "http_protocol": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword"
                  }
                }
              },
              "http_scheme": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword"
                  }
                }
              },
              "id": {
                "type": "integer"
              },
              "language": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword",
                    "ignore_above": 256
                  }
                }
              },
              "method_pool": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword",
                    "ignore_above": 256
                  }
                }
              },
              "pool_sign": {
                "type": "keyword"
              },
              "project_name": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword",
                    "ignore_above": 256
                  }
                }
              },
              "project_version_id": {
                "type": "long"
              },
              "req_data": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword",
                    "ignore_above": 256
                  }
                }
              },
              "req_header": {
                "type": "text"
              },
              "req_header_for_search": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword",
                    "ignore_above": 256
                  }
                }
              },
              "req_params": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword",
                    "ignore_above": 256
                  }
                }
              },
              "res_body": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword",
                    "ignore_above": 256
                  }
                }
              },
              "res_header": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword",
                    "ignore_above": 256
                  }
                }
              },
              "token": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword",
                    "ignore_above": 256
                  }
                }
              },
              "update_time": {
                "type": "date",
                "ignore_malformed": false,
                "format": "strict_date_optional_time||epoch_second"
              },
              "uri": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword"
                  }
                }
              },
              "uri_sha1": {
                "type": "keyword"
              },
              "url": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword"
                  }
                }
              },
              "user_id": {
                "type": "long"
              }
            }
          }
        }
      }'
      
      
      #template-dongtai-v1-vulnerability
      curl -H 'content-Type:application/json' -XPUT ${ES_HOST}/_template/${ES_ALIAS}-dongtai-v1-vulnerability-template?include_type_name -d '
      {
        "order": 1,
        "index_patterns": [
          "'${ES_ALIAS}'-dongtai-v1-vulnerability-index-*"
        ],
        "settings": {
          "index": {
            "lifecycle": {
              "name": "'${ES_ALIAS}'-dongtai-ilm-policy",
              "rollover_alias": "'${ES_ALIAS}'-alias-dongtai-v1-vulnerability"
            },
            "highlight": {
              "max_analyzed_offset": "10000000"
            },
            "refresh_interval": "30s",
            "analysis": {
              "analyzer": {
                "ngram_analyzer": {
                  "tokenizer": "ngram_tokenizer"
                }
              },
              "tokenizer": {
                "ngram_tokenizer": {
                  "token_chars": [
                    "letter",
                    "digit",
                    "symbol",
                    "punctuation"
                  ],
                  "min_gram": "1",
                  "type": "ngram",
                  "max_gram": "2"
                }
              }
            },
            "number_of_shards": "4",
            "number_of_replicas": "1"
          }
        },
        "mappings": {
          "_doc": {
            "dynamic": "true",
            "_meta": {},
            "_source": {
              "includes": [],
              "excludes": []
            },
            "dynamic_date_formats": [
              "strict_date_optional_time",
              "yyyy/MM/dd HH:mm:ss Z||yyyy/MM/dd Z"
            ],
            "dynamic_templates": [],
            "date_detection": true,
            "numeric_detection": false,
            "properties": {
              "@timestamp": {
                "type": "date"
              },
              "agent_id": {
                "type": "integer"
              },
              "bind_project_id": {
                "type": "integer"
              },
              "bottom_stack": {
                "type": "text"
              },
              "client_ip": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword"
                  }
                }
              },
              "context_path": {
                "type": "text"
              },
              "counts": {
                "type": "integer"
              },
              "first_time": {
                "type": "date",
                "ignore_malformed": false,
                "format": "strict_date_optional_time||epoch_second"
              },
              "full_stack": {
                "type": "text"
              },
              "hook_type_id": {
                "type": "integer"
              },
              "http_method": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword"
                  }
                }
              },
              "http_protocol": {
                "type": "text"
              },
              "http_scheme": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword"
                  }
                }
              },
              "id": {
                "type": "integer"
              },
              "is_del": {
                "type": "integer"
              },
              "language": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword",
                    "ignore_above": 256
                  }
                }
              },
              "latest_time": {
                "type": "date",
                "ignore_malformed": false,
                "format": "strict_date_optional_time||epoch_second"
              },
              "latest_time_desc": {
                "type": "integer"
              },
              "level_id": {
                "type": "integer"
              },
              "level_id_desc": {
                "type": "integer"
              },
              "method_pool_id": {
                "type": "integer"
              },
              "param_name": {
                "type": "text"
              },
              "project_name": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword",
                    "ignore_above": 256
                  }
                }
              },
              "project_version_id": {
                "type": "integer"
              },
              "req_data": {
                "type": "text"
              },
              "req_header": {
                "type": "text"
              },
              "req_params": {
                "type": "text"
              },
              "res_body": {
                "type": "text"
              },
              "res_header": {
                "type": "text"
              },
              "search_keywords": {
                "type": "text"
              },
              "status": {
                "type": "text"
              },
              "status_id": {
                "type": "integer"
              },
              "strategy_id": {
                "type": "integer"
              },
              "taint_position": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword"
                  }
                }
              },
              "taint_value": {
                "type": "text"
              },
              "token": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword",
                    "ignore_above": 256
                  }
                }
              },
              "top_stack": {
                "type": "text"
              },
              "uri": {
                "type": "text"
              },
              "url": {
                "type": "text"
              },
              "user_id": {
                "type": "integer"
              },
              "vul_title": {
                "type": "text"
              }
            }
          }
        }
      }'
      
      #template-dongtai-v1-asset
      curl -H 'content-Type:application/json' -XPUT ${ES_HOST}/_template/${ES_ALIAS}-dongtai-v1-asset-template?include_type_name -d '
      {
        "order": 1,
        "index_patterns": [
          "'${ES_ALIAS}'-dongtai-v1-asset-index-*"
        ],
        "settings": {
          "index": {
            "lifecycle": {
              "name": "'${ES_ALIAS}'-dongtai-ilm-policy",
              "rollover_alias": "'${ES_ALIAS}'-alias-dongtai-v1-asset"
            },
            "highlight": {
              "max_analyzed_offset": "10000000"
            },
            "refresh_interval": "30s",
            "analysis": {
              "analyzer": {
                "ngram_analyzer": {
                  "tokenizer": "ngram_tokenizer"
                }
              },
              "tokenizer": {
                "ngram_tokenizer": {
                  "token_chars": [
                    "letter",
                    "digit",
                    "symbol",
                    "punctuation"
                  ],
                  "min_gram": "1",
                  "type": "ngram",
                  "max_gram": "2"
                }
              }
            },
            "number_of_shards": "4",
            "number_of_replicas": "1"
          }
        },
        "mappings": {
          "_doc": {
            "dynamic": "true",
            "_meta": {},
            "_source": {
              "includes": [],
              "excludes": []
            },
            "dynamic_date_formats": [
              "strict_date_optional_time",
              "yyyy/MM/dd HH:mm:ss Z||yyyy/MM/dd Z"
            ],
            "dynamic_templates": [],
            "date_detection": true,
            "numeric_detection": false,
            "properties": {
              "@timestamp": {
                "type": "date"
              },
              "agent_id": {
                "type": "long"
              },
              "department_id": {
                "type": "long"
              },
              "dependency_level": {
                "type": "long"
              },
              "dt": {
                "type": "date",
                "ignore_malformed": false,
                "format": "strict_date_optional_time||epoch_second"
              },
              "id": {
                "type": "long"
              },
              "is_del": {
                "type": "long"
              },
              "language": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword",
                    "ignore_above": 256
                  }
                }
              },
              "last_version": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword",
                    "ignore_above": 256
                  }
                }
              },
              "level_id": {
                "type": "long"
              },
              "license": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword",
                    "ignore_above": 256
                  }
                }
              },
              "package_name": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword",
                    "ignore_above": 256
                  }
                }
              },
              "package_path": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword",
                    "ignore_above": 256
                  }
                }
              },
              "parent_dependency_id": {
                "type": "long"
              },
              "project_id": {
                "type": "long"
              },
              "project_name": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword",
                    "ignore_above": 256
                  }
                }
              },
              "project_version_id": {
                "type": "long"
              },
              "safe_version": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword",
                    "ignore_above": 256
                  }
                }
              },
              "signature_algorithm": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword",
                    "ignore_above": 256
                  }
                }
              },
              "signature_value": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword",
                    "ignore_above": 256
                  }
                }
              },
              "talent_id": {
                "type": "long"
              },
              "user_id": {
                "type": "long"
              },
              "version": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword",
                    "ignore_above": 256
                  }
                }
              },
              "vul_count": {
                "type": "long"
              },
              "vul_critical_count": {
                "type": "long"
              },
              "vul_high_count": {
                "type": "long"
              },
              "vul_info_count": {
                "type": "long"
              },
              "vul_low_count": {
                "type": "long"
              },
              "vul_medium_count": {
                "type": "long"
              }
            }
          }
        }
      }'
      
      #template-dongtai-v1-asset-vul
      curl -H 'content-Type:application/json' -XPUT ${ES_HOST}/_template/${ES_ALIAS}-dongtai-v1-asset-vul-template?include_type_name -d '
      {
        "order": 1,
        "index_patterns": [
          "'${ES_ALIAS}'-dongtai-v1-asset-vul-index-*"
        ],
        "settings": {
          "index": {
            "lifecycle": {
              "name": "'${ES_ALIAS}'-dongtai-ilm-policy",
              "rollover_alias": "'${ES_ALIAS}'-alias-dongtai-v1-asset-vul"
            },
            "highlight": {
              "max_analyzed_offset": "10000000"
            },
            "refresh_interval": "30s",
            "analysis": {
              "analyzer": {
                "ngram_analyzer": {
                  "tokenizer": "ngram_tokenizer"
                }
              },
              "tokenizer": {
                "ngram_tokenizer": {
                  "token_chars": [
                    "letter",
                    "digit",
                    "symbol",
                    "punctuation"
                  ],
                  "min_gram": "1",
                  "type": "ngram",
                  "max_gram": "2"
                }
              }
            },
            "number_of_shards": "4",
            "number_of_replicas": "1"
          }
        },
        "mappings": {
          "_doc": {
            "dynamic": "true",
            "_meta": {},
            "_source": {
              "includes": [],
              "excludes": []
            },
            "dynamic_date_formats": [
              "strict_date_optional_time",
              "yyyy/MM/dd HH:mm:ss Z||yyyy/MM/dd Z"
            ],
            "dynamic_templates": [],
            "date_detection": true,
            "numeric_detection": false,
            "properties": {
              "@timestamp": {
                "type": "date"
              },
              "agent_id": {
                "type": "long"
              },
              "aql": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword"
                  }
                }
              },
              "asset_agent_id": {
                "type": "integer"
              },
              "asset_id": {
                "type": "long"
              },
              "asset_project_id": {
                "type": "integer"
              },
              "asset_project_version_id": {
                "type": "integer"
              },
              "asset_user_id": {
                "type": "integer"
              },
              "asset_vul_id": {
                "type": "integer"
              },
              "asset_vul_relation_id": {
                "type": "integer"
              },
              "asset_vul_relation_is_del": {
                "type": "integer"
              },
              "bind_project_id": {
                "type": "long"
              },
              "clent_ip": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword",
                    "ignore_above": 256
                  }
                }
              },
              "context_path": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword",
                    "ignore_above": 256
                  }
                }
              },
              "create_time": {
                "type": "date",
                "ignore_malformed": false,
                "format": "strict_date_optional_time||epoch_second"
              },
              "cve_code": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword"
                  }
                }
              },
              "cve_id": {
                "type": "integer",
                "ignore_malformed": false,
                "coerce": true
              },
              "have_article": {
                "type": "integer"
              },
              "have_poc": {
                "type": "integer"
              },
              "http_method": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword",
                    "ignore_above": 256
                  }
                }
              },
              "http_protocol": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword",
                    "ignore_above": 256
                  }
                }
              },
              "http_scheme": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword",
                    "ignore_above": 256
                  }
                }
              },
              "id": {
                "type": "long"
              },
              "language": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword",
                    "ignore_above": 256
                  }
                }
              },
              "level_id": {
                "type": "integer"
              },
              "license": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword"
                  }
                }
              },
              "license_level": {
                "type": "integer"
              },
              "method_pool": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword",
                    "ignore_above": 256
                  }
                }
              },
              "package_hash": {
                "type": "keyword"
              },
              "package_language": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword"
                  }
                }
              },
              "package_latest_version": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword"
                  }
                }
              },
              "package_name": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword"
                  }
                }
              },
              "package_safe_version": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword"
                  }
                }
              },
              "package_version": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword"
                  }
                }
              },
              "pool_sign": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword",
                    "ignore_above": 256
                  }
                }
              },
              "project_id": {
                "type": "long"
              },
              "project_version_id": {
                "type": "long"
              },
              "req_data": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword",
                    "ignore_above": 256
                  }
                }
              },
              "req_header": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword",
                    "ignore_above": 256
                  }
                }
              },
              "req_header_for_search": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword",
                    "ignore_above": 256
                  }
                }
              },
              "req_params": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword",
                    "ignore_above": 256
                  }
                }
              },
              "res_body": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword",
                    "ignore_above": 256
                  }
                }
              },
              "res_header": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword",
                    "ignore_above": 256
                  }
                }
              },
              "search_title": {
                "type": "text"
              },
              "update_time": {
                "type": "date",
                "ignore_malformed": false,
                "format": "strict_date_optional_time||epoch_second"
              },
              "update_time_desc": {
                "type": "integer",
                "ignore_malformed": false,
                "coerce": true
              },
              "uri_sha1": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword",
                    "ignore_above": 256
                  }
                }
              },
              "url": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword",
                    "ignore_above": 256
                  }
                }
              },
              "user_id": {
                "type": "long"
              },
              "vul_cve_nums": {
                "type": "text"
              },
              "vul_detail": {
                "type": "text"
              },
              "vul_name": {
                "type": "text"
              },
              "vul_publish_time": {
                "type": "date",
                "ignore_malformed": false,
                "format": "strict_date_optional_time||epoch_second"
              },
              "vul_serial": {
                "type": "text"
              },
              "vul_update_time": {
                "type": "date",
                "ignore_malformed": false,
                "format": "strict_date_optional_time||epoch_second"
              }
            }
          }
        }
      }'
      
      
      #template-dongtai-v1-asset-vul
      curl -H 'content-Type:application/json' -XPUT ${ES_HOST}/_template/${ES_ALIAS}-dongtai-v1-asset-aggr-template?include_type_name -d '
      {
        "order": 1,
        "index_patterns": [
          "'${ES_ALIAS}'-dongtai-v1-asset-aggr-index-*"
        ],
        "settings": {
          "index": {
            "lifecycle": {
              "name": "'${ES_ALIAS}'-dongtai-ilm-policy",
              "rollover_alias": "'${ES_ALIAS}'-alias-dongtai-v1-asset-aggr"
            },
            "highlight": {
              "max_analyzed_offset": "10000000"
            },
            "refresh_interval": "30s",
            "analysis": {
              "analyzer": {
                "ngram_analyzer": {
                  "tokenizer": "ngram_tokenizer"
                }
              },
              "tokenizer": {
                "ngram_tokenizer": {
                  "token_chars": [
                    "letter",
                    "digit",
                    "symbol",
                    "punctuation"
                  ],
                  "min_gram": "1",
                  "type": "ngram",
                  "max_gram": "2"
                }
              }
            },
            "number_of_shards": "4",
            "number_of_replicas": "1"
          }
        },
        "mappings": {
          "_doc": {
            "dynamic": "true",
            "_meta": {},
            "_source": {
              "includes": [],
              "excludes": []
            },
            "dynamic_date_formats": [
              "strict_date_optional_time",
              "yyyy/MM/dd HH:mm:ss Z||yyyy/MM/dd Z"
            ],
            "dynamic_templates": [],
            "date_detection": true,
            "numeric_detection": false,
            "properties": {
              "@timestamp": {
                "type": "date"
              },
              "id": {
                "type": "integer"
              },
              "is_del": {
                "type": "integer"
              },
              "language": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword"
                  }
                }
              },
              "last_version": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword"
                  }
                }
              },
              "level_id": {
                "type": "integer"
              },
              "license": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword"
                  }
                }
              },
              "package_name": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword"
                  }
                }
              },
              "project_count": {
                "type": "integer"
              },
              "safe_version": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword"
                  }
                }
              },
              "signature_value": {
                "type": "keyword"
              },
              "version": {
                "type": "text",
                "fields": {
                  "keyword": {
                    "type": "keyword"
                  }
                }
              },
              "vul_count": {
                "type": "integer"
              },
              "vul_critical_count": {
                "type": "integer"
              },
              "vul_high_count": {
                "type": "integer"
              },
              "vul_info_count": {
                "type": "integer"
              },
              "vul_low_count": {
                "type": "integer"
              },
              "vul_medium_count": {
                "type": "integer"
              }
            }
          }
        }
      }'
      
      curl -H 'content-Type:application/json' -XPUT ${ES_HOST}/${ES_ALIAS}-dongtai-v1-method-pool-index-000001 -d '
      {
        "aliases": {
          "'${ES_ALIAS}'-alias-dongtai-v1-method-pool": {
            "is_write_index": true
          }
        }
      }'
      
      curl -H 'content-Type:application/json' -XPUT ${ES_HOST}/${ES_ALIAS}-dongtai-v1-vulnerability-index-000001 -d '
      {
        "aliases": {
          "'${ES_ALIAS}'-alias-dongtai-v1-vulnerability": {
            "is_write_index": true
          }
        }
      }'
      
      curl -H 'content-Type:application/json' -XPUT ${ES_HOST}/${ES_ALIAS}-dongtai-v1-asset-index-000001 -d '
      {
        "aliases": {
          "'${ES_ALIAS}'-alias-dongtai-v1-asset": {
            "is_write_index": true
          }
        }
      }'
      
      curl -H 'content-Type:application/json' -XPUT ${ES_HOST}/${ES_ALIAS}-dongtai-v1-asset-aggr-index-000001 -d '
      {
        "aliases": {
          "'${ES_ALIAS}'-alias-dongtai-v1-asset-aggr": {
            "is_write_index": true
          }
        }
      }'
      
      curl -H 'content-Type:application/json' -XPUT ${ES_HOST}/${ES_ALIAS}-dongtai-v1-asset-vul-index-000001 -d '
      {
        "aliases": {
          "'${ES_ALIAS}'-alias-dongtai-v1-asset-vul": {
            "is_write_index": true
          }
        }
      }'
      Info "index created Ok !!!"
      Notice "-----index created Ok !!!-----"
    }
    
    dongtai_es
    dongtai_index

    ;;

  *) # Invalid subcommand
    if [ ! -z $subcommand ]; then # Don't show if no subcommand provided
      echo "Invalid subcommand: $subcommand"
    fi
    usage
    exit 1 # Exit with error
    ;;
  esac
else # else if no options provided throw error
  usage
  exit 1
fi